<template>
    <div class="table-query-form">
        <el-form :inline="true" label-width="100" class="query-form-wrapper">
            <template v-if="queryFormItems.length !== 0">
                <template v-for="(item, index) in queryFormItems" :key="index">
                    <!-- text类型 -->
                    <el-form-item :label="item.label" v-if="item.type === 'text' || item.type === undefined">
                        <el-input v-if="item.component === undefined" v-model="item.value" :placeholder="item.placeholder" clearable></el-input>
                        <component v-else :is="item.component"></component>
                    </el-form-item>
                    <!-- number类型 -->
                    <el-form-item v-else-if="item.type === 'number'" :label="item.label">
                        <el-input-number
                            v-if="item.component === undefined"
                            :min="0"
                            v-model="item.value"
                            :placeholder="item.placeholder"
                        ></el-input-number>
                        <component v-else :is="item.component"></component>
                    </el-form-item>
                    <!-- select类型 -->
                    <el-form-item :label="item.label" v-else-if="item.type === 'select'">
                        <el-select v-model="item.value" clearable v-if="item.options && item.options().length !== 0 && item.component === undefined">
                            <el-option v-for="(option, index) in item.options()" :key="index" :label="option.label" :value="option.value"></el-option>
                        </el-select>
                        <component v-else :is="item.component"></component>
                    </el-form-item>
                    <!-- boole类型 -->
                    <el-form-item :label="item.label" v-if="item.type === 'boole'">
                        <el-select v-model="item.value" :placeholder="item.placeholder" clearable v-if="item.component === undefined">
                            <template v-if="item.options && item.options()?.length !== 0">
                                <el-option
                                    v-for="(option, index) in item.options()"
                                    :key="index"
                                    :label="option.label"
                                    :value="option.value"
                                ></el-option>
                            </template>
                            <template v-else>
                                <el-option label="是" :value="true"></el-option>
                                <el-option label="否" :value="false"></el-option>
                            </template>
                        </el-select>
                        <component v-else :is="item.component"></component>
                    </el-form-item>
                    <!-- datetime类型 -->
                    <el-form-item
                        :label="item.label"
                        v-else-if="item.type === 'datetime'"
                        :class="item.dateType?.includes('range') ? 'datetimeRange' : 'datetime'"
                    >
                        <el-date-picker
                            v-if="item.component === undefined"
                            v-model="item.value"
                            :type="item.dateType"
                            range-separator="至"
                            start-placeholder="开始时间"
                            end-placeholder="结束时间"
                            :placeholder="item.placeholder ?? '请选择'"
                            format="YYYY-MM-DD HH:mm:ss"
                            value-format="YYYY-MM-DD HH:mm:ss"
                            date-format="YYYY-MM-DD"
                            time-format="HH:mm:ss"
                        />
                        <component v-else :is="item.component"></component>
                    </el-form-item>
                    <!-- 范围 -->
                    <el-form-item :label="item.label" v-if="item.type === 'range'">
                        <div v-if="item.component === undefined" class="number-range-input">
                            <el-input-number
                                v-model="rangeArr[0]"
                                placeholder="开始值"
                                :step="1"
                                :min="0"
                                :max="rangeArr[1] - 1"
                                :controls="false"
                            ></el-input-number>
                            <span>至</span>
                            <el-input-number
                                v-model="rangeArr[1]"
                                placeholder="结束值"
                                :step="1"
                                :min="rangeArr[0] + 1"
                                :controls="false"
                            ></el-input-number>
                        </div>
                        <component v-else :is="item.component"></component>
                    </el-form-item>
                    <!-- 地址 -->
                    <el-form-item :label="item.label" v-if="item.type === 'address'">
                        <el-cascader v-if="item.component === undefined" v-model="item.value" :options="regions" :props="regionsProps" clearable />
                        <component v-else :is="item.component"></component>
                    </el-form-item>
                </template>
            </template>
            <el-form-item label=" ">
                <el-button type="primary" @click="onQueryHandle">查询</el-button>
                <el-button type="default" @click="onResetHandle">重置</el-button>
            </el-form-item>
        </el-form>
    </div>
</template>

<script setup lang="ts">
import { QueryFormItem, QueryCondition, QueryFormType } from '@/types/queryform'

interface Props {
    queryFormItems: QueryFormItem<any>[]
}
const props = defineProps<Props>()

const emit = defineEmits<{ onQuerySubmit: [action: TableActionType, params: any] }>()
const rangeArr = ref<number[]>([])
const queryForm = reactive<QueryFormType<any>>({
    sort: 'createDateTime',
    order: true,
    queryConditions: [],
})
onMounted(() => {
    getRegionsData()
})

const regions = ref<any[]>()
const regionsProps = { label: 'name', value: 'name', children: 'children' }

const getRegionsData = async () => {
    const addressIndex = props.queryFormItems.findIndex((e) => e.type === 'address')
    if (addressIndex < 0) {
        return
    }
    const result = await getRegions()
    if (result.isSuccess) {
        regions.value = result.data
    }
}
// 表单提交
const onQueryHandle = () => {
    // 重置查询条件
    Object.assign(queryForm, { sort: undefined, order: undefined, queryConditions: [] })
    props.queryFormItems.forEach((item) => {
        if (item.value === undefined || item.value === null) {
            if (item.type === 'range' && rangeArr.value.length === 2 && rangeArr.value.every((e) => e !== null)) {
                getQueryCondition(item)
            } else {
                return
            }
        } else if (item.sort === 'Sort') {
            queryForm.sort = item.value
        } else if (item.sort === 'Order') {
            queryForm.order = item.value
        } else {
            getQueryCondition(item)
        }
    })
    if (queryForm.queryConditions.length !== 0 || queryForm.sort !== undefined || queryForm.order !== undefined) {
        emit('onQuerySubmit', 'query-form-submit', queryForm)
    } else {
        ElMessage.warning('请先填写必要的查询条件')
    }
}
// 获得查询条件
const getQueryCondition = (item: QueryFormItem<any>) => {
    let form: QueryCondition = { name: '', value: '', operator: 'Equal' }
    switch (item.type) {
        case 'number':
            form = { name: item.name as string, value: item.value, operator: item.operator ?? 'Equal' }
            break
        case 'boole':
            form = { name: item.name as string, value: item.value, operator: item.operator ?? 'Equal' }
            break
        case 'select':
            form = { name: item.name as string, value: item.value, operator: item.operator ?? 'Equal' }
            break
        case 'datetime': {
            if ((item.dateType as string).includes('range')) {
                form = { name: item.name as string, value: item.value[0], operator: item.operator ?? 'Range', secondValue: item.value[1] }
            } else {
                form = { name: item.name as string, value: item.value, operator: item.operator ?? 'GreaterThanOrEqual' }
            }
            break
        }
        case 'range': {
            if (rangeArr.value.length === 2) {
                form = { name: item.name as string, value: rangeArr.value[0], operator: item.operator ?? 'Range', secondValue: rangeArr.value[1] }
            }
            break
        }
        case 'address': {
            form = { name: item.name as string, value: JSON.stringify(item.value), operator: item.operator ?? 'Equal' }
            break
        }
        default:
            form = { name: item.name as string, value: item.value, operator: item.operator ?? 'Contains' }
            break
    }
    if (form.name !== '' && form.value !== '') {
        queryForm.queryConditions.push(form)
    }
}

// 表单重置
const onResetHandle = () => {
    // 表单重置
    resetQueryForm(props.queryFormItems)
    rangeArr.value = []
    // 重置查询条件
    Object.assign(queryForm, { sort: 'createDateTime', order: true, queryConditions: [] })
    emit('onQuerySubmit', 'query-form-submit', queryForm)
}

// 组件卸载清空数据
onUnmounted(() => {
    // 表单重置
    resetQueryForm(props.queryFormItems)
    rangeArr.value = []
    // 重置查询条件
    Object.assign(queryForm, { sort: undefined, order: undefined, queryConditions: [] })
})
</script>

<style lang="scss" scoped>
.table-query-form {
    border: 1px solid var(--el-border-color-lighter);
    border-bottom: none;
    padding: 10px;
    overflow: hidden;

    .el-form-item {
        width: 280px;

        .el-input-number {
            width: 180px;
        }
        .el-input {
            width: 180px;
        }
        .el-select {
            width: 180px;
        }

        &.datetime {
            width: 280px;
        }
        &.datetimeRange {
            width: 592px; // 180 * 2 + 100 * 2 + 32
        }

        .number-range-input {
            width: 260px;
            display: flex;
            justify-content: space-between;
            align-items: center;

            .el-input-number {
                width: 80px;
            }
        }
    }
}
</style>
